package cn.ligoo.part.web.springmvc.platform;

import java.io.File;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import javax.annotation.Resource;
import javax.servlet.ServletContext;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.commons.io.FileUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.context.MessageSource;
import org.springframework.dao.DataAccessException;
import org.springframework.dao.DuplicateKeyException;
import org.springframework.stereotype.Controller;
import org.springframework.util.StringUtils;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.multipart.MaxUploadSizeExceededException;
import org.springframework.web.multipart.MultipartFile;
import org.springframework.web.multipart.MultipartHttpServletRequest;

import ssm.core.util.FileNaming;
import ssm.core.util.FileNamingUtils;
import cn.ligoo.part.domain.PartInfo;
import cn.ligoo.part.service.impl.FacadeImpl;
import cn.ligoo.part.web.Constants;
import cn.ligoo.part.web.FileUploadUtils;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.serializer.SerializeConfig;
import com.alibaba.fastjson.serializer.SimpleDateFormatSerializer;

@Controller
@RequestMapping("/platform/part-info")
public class PartInfoController {
	private final Logger logger = LoggerFactory.getLogger(PartInfoController.class);

	@Resource
	private MessageSource message;

	@Resource
	private FacadeImpl facade;

	public PartInfoController() {
		logger.debug("...constructor");
	}

	@ExceptionHandler(Exception.class)
	@ResponseBody
	public String handleException(Exception ex, HttpServletRequest request) {
		logger.debug("...handleException");
		String msg = null;
		if (ex instanceof MaxUploadSizeExceededException) {
			MaxUploadSizeExceededException museex = (MaxUploadSizeExceededException) ex;
			logger.debug("...ex instanceof org.springframework.web.multipart.MaxUploadSizeExceededException");

			Object[] params = new Object[] { FileUtils.byteCountToDisplaySize(museex.getMaxUploadSize()) };
			msg = message.getMessage("exception.maxUploadExceeded", params, null);
		} else {
			logger.error("{}", ex);
			msg = ex.getMessage();
		}
		return String.format(Constants.JSON_ERROR, msg);
	}

	@RequestMapping(value = "/search", produces = "text/html;charset=UTF-8", method = RequestMethod.POST)
	@ResponseBody
	public String search(HttpServletRequest request, @RequestParam int page, @RequestParam int rows, PartInfo t) {
		logger.debug("...search");

		logger.debug("...page:{},rows:{}", page, rows);
		logger.debug("...partInfo:{}", t.toString());

		int total = facade.getPartInfoService().getPartInfoCount(t);

		t.getRow().setOffset((page - 1) * rows);
		t.getRow().setLimit(rows);
		List<PartInfo> partInfoList = facade.getPartInfoService().getPartInfoList(t);

		SerializeConfig sc = new SerializeConfig();
		sc.put(Date.class, new SimpleDateFormatSerializer("yyyy-MM-dd"));

		String json = String.format(Constants.JSON_DATAGRID, JSON.toJSONString(partInfoList, sc), total);
		logger.debug("...json:{}", json);
		return json;
	}

	@RequestMapping(value = "/export", produces = "text/html;charset=UTF-8", method = RequestMethod.GET)
	@ResponseBody
	public String export(HttpServletRequest request, HttpServletResponse response, PartInfo t) {
		logger.debug("...export");
		String filename = "part.xls";

		response.setContentType("application/octet-stream");
		response.setHeader("Content-Disposition", "attachment; filename=\"" + filename + "\"");

		logger.debug("...partInfo:{}", t.toString());
		List<PartInfo> partInfoList = facade.getPartInfoService().getPartInfoList(t);

		Map<String, Object> model = new HashMap<String, Object>();
		model.put("partInfoList", partInfoList);

		String content = facade.getTemplateService().getContent("/" + filename + ".ftl", model);
		logger.debug("...content:{}", content);
		return content;
	}

	@RequestMapping(value = "/delete", produces = "text/html;charset=UTF-8", method = RequestMethod.GET)
	@ResponseBody
	public String delete(@RequestParam String[] ids) {
		logger.debug("...delete ids:{}", ids);
		PartInfo t = new PartInfo();
		t.getMap().put("__ids", ids);
		t.getMap().put("__isLogicalDelete", "true");

		int count = 0;
		try {
			count = facade.getPartInfoService().removePartInfo(t);
		} catch (DataAccessException dae) {
			String msg = message.getMessage("errors.dae", null, null);
			return String.format(Constants.JSON_ERROR, msg);
		}
		return String.format(Constants.JSON_SUCCESS, null, count);
	}

	@RequestMapping(value = "/save", produces = "text/html;charset=UTF-8", method = RequestMethod.POST)
	@ResponseBody
	public String save(MultipartHttpServletRequest request, PartInfo partInfo, MultipartFile part_data_file) {
		logger.debug("...save");
		logger.debug("partInfo:{}", partInfo.toString());

		if (null == part_data_file || part_data_file.getSize() == 0) {
			partInfo.setPart_data("");// 不传文件，就设置为null
		} else {
			logger.debug("part_data_file:{}", part_data_file.getOriginalFilename());

			String fileSaveName = FileNamingUtils.getFileName(part_data_file.getOriginalFilename(), FileNaming.UUID);
			String fileSavePath;
			File file;
			try {
				ServletContext context = request.getSession(true).getServletContext();
				fileSavePath = FileUploadUtils.getUploadFileSavePath(context);
				file = new File(FileUploadUtils.getUploadFileFullSavePath(context), fileSaveName);
				FileUtils.writeByteArrayToFile(file, part_data_file.getBytes());
			} catch (FileNotFoundException fnfex) {
				logger.error(fnfex.getMessage());
				return String.format(Constants.JSON_ERROR, "FileNotFoundException");
			} catch (IOException ioex) {
				logger.error(ioex.getMessage());
				return String.format(Constants.JSON_ERROR, "IOException");
			}
			partInfo.setPart_data(StringUtils.replace(fileSavePath + fileSaveName, File.separator,
					FileUploadUtils.UPLOAD_FILE_SEPARATOR));
		}
		partInfo.setCreate_time(new Date());
		partInfo.setOrder_value(Constants.SHORT_0);
		// partInfo.setIs_lock(Constants.BYTE_0);
		try {
			if (null == partInfo.getId()) {
				partInfo.setCreate_time(new Date());
				facade.getPartInfoService().createPartInfo(partInfo);
			} else {
				facade.getPartInfoService().modifyPartInfo(partInfo);
			}
		} catch (DuplicateKeyException dke) {
			String msg = message.getMessage("errors.dae.DuplicateKeyException", null, null);
			return String.format(Constants.JSON_ERROR, msg);
		} catch (DataAccessException dae) {
			String msg = message.getMessage("errors.dae", null, null);
			return String.format(Constants.JSON_ERROR, msg);
		}
		return String.format(Constants.JSON_SUCCESS, null, null);
	}

	@RequestMapping(value = "/edit/{id}", produces = "text/html;charset=UTF-8", method = RequestMethod.GET)
	@ResponseBody
	public String edit(@PathVariable Integer id) {
		logger.debug("...edit");
		PartInfo t = new PartInfo();
		t.setId(id);
		PartInfo partInfo = facade.getPartInfoService().getPartInfo(t);
		logger.debug("...partInfo:{}", partInfo);

		SerializeConfig sc = new SerializeConfig();
		sc.put(Date.class, new SimpleDateFormatSerializer("yyyy-MM-dd"));
		return JSON.toJSONString(partInfo, sc);
	}
}
